﻿using System;
using System.Linq;
using System.Collections.Generic;
using System.Threading.Tasks;
using BestEasy.CMS.Services.Interfaces.Security;
using BestEasy.CMS.Services.Messaging.Request.Security;
using BestEasy.CMS.Services.Messaging.Response;
using BestEasy.CMS.Services.ViewModels.Security;
using BestEasy.CMS.Services.Mapping;
using BestEasy.CMS.Models.Security;

using BestEasy.Core;
using BestEasy.Core.UnitOfWork;
using BestEasy.Core.Extensions;
using BestEasy.Core.Pageing;
using BestEasy.CMS.Services.Messaging.Response.Security;

namespace BestEasy.CMS.Services.Implementations.Security
{
    public class UserService : IUserService
    {
        #region 属性
        private readonly IUserRepository _userRepository;
        private readonly IUnitOfWork _unitOfWork;
        #endregion

        #region  构造函数
        public UserService(IUserRepository userRepository, IUnitOfWork unitOfWork)
        {
            _userRepository = userRepository;
            _unitOfWork = unitOfWork;
        }
        #endregion

        #region 方法
        public ResponseBase Save(UserView view, SaveType type)
        {
            if (view == null)
                throw new ArgumentNullException(nameof(view));
            var response = new ResponseBase();
            try
            {
                var entity = view.ToEntity<User, UserView>();
                if (type == SaveType.Update)
                    _userRepository.Update(entity);
                else
                    _userRepository.Insert(entity);
                _unitOfWork.Commit();
                response.IsSuccess = true;
            }
            catch (BestEasyException ex)
            {
                response.IsSuccess = false;
                response.Message = ex.Message;
            }
            return response;
        }

        public Task<ResponseBase> SaveAsync(UserView view, SaveType type)
        {
            throw new NotImplementedException();
        }

        public ResponseBase InsertBulkUser(IEnumerable<UserView> views)
        {
            if (views == null)
                throw new ArgumentNullException(nameof(views));
            var response = new ResponseBase();
            try
            {
                _userRepository.InsertBulk(views.ToEntitys<User, UserView>());
                response.IsSuccess = true;
            }
            catch (BestEasyException ex)
            {
                response.IsSuccess = false;
                response.Message = ex.Message;
            }
            return response;
        }
        public ResponseBase Delete(long id)
        {
            var response = new ResponseBase();
            if (id == 0)
                return response;
            var user = _userRepository.GetById(id);
            if (user == null)
                return response;
            if (user.IsSystemUser)
                throw new BestEasyException($"无法删除系统帐号（{user.LoginName}）");

            var result = _userRepository.Delete(id);
            return new ResponseBase { IsSuccess = result > 0 };
        }
        public ResponseBase TakeDelete(long id)
        {
            var response = new ResponseBase();
            if (id == 0)
                return response;
            var user = _userRepository.GetById(id);
            if (user == null)
                return response;
            if (user.IsSystemUser)
                throw new BestEasyException($"无法删除系统帐号（{user.LoginName}）");
            try
            {
                var result = _userRepository.UpdateMany().Where(p => p.Id == id).OnlyFields(p => p.IsDel).Execute(new User { IsDel = true });
                response.IsSuccess = result > 0;
            }
            catch (BestEasyException ex)
            {
                response.IsSuccess = false;
                response.Message = ex.Message;
            }
            return response;
        }

        public GetPageResponse<UserView> GetByPage(Paged page)
        {
            throw new NotImplementedException();
        }
        public GetPageResponse<UserView> GetUsers(GetUserPageRequest request)
        {
            if (request == null)
                throw new ArgumentNullException(nameof(request));

            var response = new GetPageResponse<UserView>();
            var result = _userRepository.Query().Include(p => p.Role)
                .HasWhere(request.LoginName, p => p.LoginName.Contains(request.LoginName))
                .HasWhere(request.RoleId, p => p.RoleId == request.RoleId)
                .HasWhere(request.IsEnable, p => p.IsEnable == request.IsEnable)
                .Where(p => !p.IsDel).OrderBy(p => p.RoleId)
                .ToPage(request.Paged.PageIndex, request.Paged.PageSize);
            if (result.Items.Any())
            {
                response.Message = "获取成功！";
                response.IsSuccess = true;
                response.Pages = result.ToPageView<User, UserView>();
            }
            return response;
        }
        public GetPageResponse<UserView> GetUsersByRecycleBin(Paged page)
        {
            if (page == null)
                throw new ArgumentNullException(nameof(page));

            var response = new GetPageResponse<UserView>();
            var result = _userRepository.Query().Include(p => p.Role)
                .Where(p => p.IsDel).OrderBy(p => p.RoleId)
                .ToPage(page.PageIndex, page.PageSize);
            if (result.Items.Any())
            {
                response.Message = "获取成功！";
                response.IsSuccess = true;
                response.Pages = result.ToPageView<User, UserView>();
            }
            return response;
        }
        public GetListResponse<UserView> GetUsersByRecycleBin()
        {
            var response = new GetListResponse<UserView>();
            var result = _userRepository.Query().Include(p => p.Role).Where(p => p.IsDel).OrderBy(p => p.RoleId).ToList();
            if (result.Any())
            {
                response.IsSuccess = true;
                response.Views = result.ToViews<User, UserView>();
            }
            return response;
        }
        public GetListResponse<UserView> GetAll()
        {
            var response = new GetListResponse<UserView>();
            var result = _userRepository.Query().Include(p => p.Role).Where(p => !p.IsDel).OrderBy(p => p.RoleId).ToList();
            if (result.Any())
            {
                response.IsSuccess = true;
                response.Views = result.ToViews<User, UserView>();
            }
            return response;
        }
        public GetSingleResponse<UserView> GetById(long id)
        {
            var response = new GetSingleResponse<UserView>();
            if (id == 0)
                return response;
            var result = _userRepository.GetById(id);
            if (result != null && !result.IsDel)
            {
                response.IsSuccess = true;
                response.View = result.ToView<User, UserView>();
            }
            return response;
        }

        public bool LoginNameExists(string loginName)
        {
            if (string.IsNullOrWhiteSpace(loginName))
                throw new ArgumentNullException(nameof(loginName));

            return _userRepository.Query().Any(p => p.LoginName == loginName);
        }
        public LoginResponse Login(LoginRequest request)
        {
            if (request == null)
                throw new ArgumentNullException(nameof(request));
            var response = new LoginResponse();
            var user = _userRepository.Query().Where(p => p.LoginName == request.LoginName && !p.IsDel).ToList();
            if (!user.Any())
            {
                response.Status = LoginStatus.UserDoesNotExist;
                response.Message = "用户不存在！";
                return response;
            }
            if (!user[0].IsEnable)
            {
                response.Status = LoginStatus.UserNotAvailable;
                response.Message = "用户不可用！";
                return response;
            }
            if (user[0].Password != request.Password)
            {
                response.Status = LoginStatus.UsernameOrPasswordIsWrong;
                response.Message = "用户名或密码错误！";
                return response;
            }
            response.Status = LoginStatus.Normal;
            response.UserId = user[0].Id;
            response.RoleId = user[0].RoleId;
            response.UserName = user[0].LoginName;
            response.IsSuccess = true;
            response.Message = "登录成功！";
            return response;
        }

        #endregion
    }
}
